<template>
  <div class="calculator-container" :class="theme">
    <div class="calculator">
      <div class="calculator-header">
        <button class="theme-toggle" @click="toggleTheme" :title="theme === 'dark' ? '切换明亮主题' : '切换暗黑主题'">
          <i :class="theme === 'dark' ? 'icon-sun' : 'icon-moon'"></i>
        </button>
        <button class="history-toggle" @click="toggleHistory" :title="showHistory ? '隐藏历史记录' : '显示历史记录'">
          <i class="icon-history"></i>
        </button>
      </div>

      <div class="calculator-content" :class="{ 'history-open': showHistory }">
        <div class="calculator-main">
          <div class="calculator-display" @paste="handlePaste">
            <div class="expression">{{ expression || '0' }}</div>
            <div class="result">{{ result }}</div>
          </div>

          <div class="calculator-keypad">
            <div class="row">
              <button class="func" @click="clearAll">AC</button>
              <button class="func" @click="clearLast">←</button>
              <button class="func" @click="appendPercent">%</button>
              <button class="operator" @click="appendOperator('/')">÷</button>
            </div>
            <div class="row">
              <button @click="appendNumber(7)">7</button>
              <button @click="appendNumber(8)">8</button>
              <button @click="appendNumber(9)">9</button>
              <button class="operator" @click="appendOperator('*')">×</button>
            </div>
            <div class="row">
              <button @click="appendNumber(4)">4</button>
              <button @click="appendNumber(5)">5</button>
              <button @click="appendNumber(6)">6</button>
              <button class="operator" @click="appendOperator('-')">−</button>
            </div>
            <div class="row">
              <button @click="appendNumber(1)">1</button>
              <button @click="appendNumber(2)">2</button>
              <button @click="appendNumber(3)">3</button>
              <button class="operator" @click="appendOperator('+')">+</button>
            </div>
            <div class="row">
              <button @click="appendNumber(0)">0</button>
              <button @click="appendDecimal">.</button>
              <button class="equals" @click="calculate">=</button>
            </div>
          </div>
        </div>

        <transition name="history-slide">
          <div v-show="showHistory" class="calculator-history">
            <div class="history-header">
              <h3>历史记录</h3>
              <div class="close-history button" @click="toggleHistory">
                <i class="icon-close"></i>
              </div>
            </div>
            <div class="history-items">
              <div v-for="(item, index) in history" :key="index" class="history-item" @click="loadFromHistory(item)">
                <div class="history-expression">{{ item.expression }}</div>
                <div class="history-result">{{ item.result }}</div>
              </div>
              <div v-if="history.length === 0" class="empty-history">
                暂无历史记录
              </div>
            </div>
          </div>
        </transition>
      </div>
    </div>
  </div>
</template>

  <script>
export default {
  name: "Calculator",
  data() {
    return {
      showHistory: false,
      theme: "dark",
      expression: "",
      result: "0",
      lastInputWasOperator: false,
      history: [],
      calculated: false,
    };
  },
  created() {
    const savedTheme = localStorage.getItem("calculator-theme");
    if (savedTheme) {
      this.theme = savedTheme;
    }

    const savedHistory = localStorage.getItem("calculator-history");
    if (savedHistory) {
      this.history = JSON.parse(savedHistory);
    }

    window.addEventListener("keydown", this.handleKeydown);
    document.addEventListener("paste", this.handleDocumentPaste);
  },
  beforeDestroy() {
    window.removeEventListener("keydown", this.handleKeydown);
    document.removeEventListener("paste", this.handleDocumentPaste);
  },
  methods: {
    handlePaste(e) {
      e.preventDefault();
      const clipboardData = e.clipboardData || window.clipboardData;
      const pastedText = clipboardData.getData("text/plain");
      this.processPastedText(pastedText);
    },

    handleDocumentPaste(e) {
      if (!e.target.closest(".calculator-display")) return;

      e.preventDefault();
      const clipboardData = e.clipboardData || window.clipboardData;
      const pastedText = clipboardData.getData("text/plain");
      this.processPastedText(pastedText);
    },

    processPastedText(text) {
      if (!text) return;

      this.clearAll();

      const sanitizedText = text
        .replace(/[^\d\+\-\*\/\s\.]/g, "")
        .replace(/×/g, "*")
        .replace(/÷/g, "/")
        .replace(/−/g, "-");

      if (sanitizedText) {
        this.expression = sanitizedText;
        this.calculate();
      }
    },

    appendNumber(number) {
      if (this.calculated) {
        this.clearAll();
        this.calculated = false;
      }

      if (this.result === "0" && this.expression === "") {
        this.expression = number.toString();
      } else if (this.lastInputWasOperator) {
        this.expression += number.toString();
      } else {
        this.expression += number.toString();
      }
      this.lastInputWasOperator = false;
    },

    appendDecimal() {
      if (this.calculated) {
        this.clearAll();
        this.calculated = false;
      }

      if (this.expression === "") {
        this.expression = "0.";
      } else if (this.lastInputWasOperator) {
        this.expression += "0.";
      } else {
        const lastNumberMatch = this.expression.match(/(\d+\.?\d*)$/);
        if (lastNumberMatch && !lastNumberMatch[0].includes(".")) {
          this.expression += ".";
        } else if (!lastNumberMatch) {
          this.expression += "0.";
        }
      }
      this.lastInputWasOperator = false;
    },

    appendOperator(op) {
      if (this.calculated) {
        this.expression = this.result;
        this.calculated = false;
      }

      if (this.expression === "" && op === "-") {
        this.expression = "-";
      } else if (this.expression !== "" && !this.lastInputWasOperator) {
        this.expression += ` ${op} `;
      } else if (this.lastInputWasOperator) {
        this.expression = this.expression.replace(/[\+\-\*\/]\s$/, `${op} `);
      }
      this.lastInputWasOperator = true;
    },

    appendPercent() {
      if (this.calculated) {
        this.clearAll();
        this.calculated = false;
      }

      if (this.expression === "") {
        // 如果表达式为空，直接添加0.01
        this.expression = "0.01";
      } else {
        // 获取最后一个数字或整个表达式
        const lastNumberMatch = this.expression.match(/(-?\d+\.?\d*)$/);

        if (lastNumberMatch) {
          const lastNumber = lastNumberMatch[0];
          // 计算百分比值（除以100）
          const percentValue = parseFloat(lastNumber) / 100;
          // 替换最后一个数字为百分比值
          this.expression = this.expression.replace(
            /(-?\d+\.?\d*)$/,
            percentValue.toString()
          );
        } else {
          // 如果没有匹配到数字，在表达式末尾添加0.01
          this.expression += "0.01";
        }
      }
      this.lastInputWasOperator = false;
    },

    calculate() {
      if (this.expression === "") return;

      try {
        let expr = this.expression
          .replace(/×/g, "*")
          .replace(/÷/g, "/")
          .replace(/−/g, "-");

        expr = expr.replace(/(\d+(\.\d+)?)%/g, "($1/100)");

        const safeEval = new Function("return " + expr);
        const calculatedResult = safeEval();

        this.result = Number.isInteger(calculatedResult)
          ? calculatedResult.toString()
          : parseFloat(calculatedResult.toFixed(8)).toString();

        this.addToHistory(this.expression, this.result);
        this.calculated = true;
      } catch (error) {
        this.result = "Error";
        setTimeout(() => {
          this.clearAll();
        }, 1000);
      }
      this.lastInputWasOperator = false;
    },

    addToHistory(expression, result) {
      this.history.unshift({
        expression,
        result,
        timestamp: new Date().toLocaleString(),
      });

      if (this.history.length > 10) {
        this.history.pop();
      }

      localStorage.setItem("calculator-history", JSON.stringify(this.history));
    },

    loadFromHistory(item) {
      this.expression = item.expression;
      this.result = item.result;
      this.showHistory = false;
      this.calculated = false;
    },

    clearAll() {
      this.expression = "";
      this.result = "0";
      this.lastInputWasOperator = false;
      this.calculated = false;
    },

    clearLast() {
      if (this.calculated) {
        this.clearAll();
        return;
      }

      if (this.expression.endsWith(" ")) {
        this.expression = this.expression.slice(0, -3);
      } else {
        this.expression = this.expression.slice(0, -1);
      }

      if (this.expression === "") {
        this.result = "0";
      }
      this.lastInputWasOperator = false;
    },

    clearHistory() {
      this.history = [];
      localStorage.removeItem("calculator-history");
    },

    toggleTheme() {
      this.theme = this.theme === "dark" ? "light" : "dark";
      localStorage.setItem("calculator-theme", this.theme);
    },

    toggleHistory() {
      this.showHistory = !this.showHistory;
    },

    handleKeydown(e) {
      const key = e.key;
      if (/^\d$/.test(key)) {
        this.appendNumber(parseInt(key));
      } else if (key === ".") {
        this.appendDecimal();
      } else if (key === "+" || key === "-" || key === "*" || key === "/") {
        this.appendOperator(key);
      } else if (key === "%") {
        this.appendPercent();
      } else if (key === "Enter" || key === "=") {
        this.calculate();
        e.preventDefault();
      } else if (key === "Escape") {
        if (this.showHistory) {
          this.toggleHistory();
        } else {
          this.clearAll();
        }
        e.preventDefault();
      } else if (key === "Backspace") {
        this.clearLast();
        e.preventDefault();
      } else if (key === "h" || key === "H") {
        this.toggleHistory();
      } else if (key === "t" || key === "T") {
        this.toggleTheme();
      } else if (e.ctrlKey && key === "v") {
        return;
      }
    },
  },
};
</script>

  <style scoped>
/* 样式保持不变，与之前相同 */
.calculator-container {
  width: 100%;
  height: 100%;
  display: flex;
  align-items: center;
  justify-content: center;
}
.calculator-container.light {
  background-color: #f1f1f1;
}

.calculator {
  border-radius: 16px;
  overflow: hidden;
  box-shadow: 0 10px 25px rgba(0, 0, 0, 0.2);
  position: relative;
  width: 320px;
}

.calculator-header {
  display: flex;
  justify-content: flex-end;
  padding: 10px 15px;
  background-color: inherit;
}

.theme-toggle,
.history-toggle {
  background: transparent;
  border: none;
  width: 36px;
  height: 36px;
  border-radius: 50%;
  font-size: 20px;
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: center;
  transition: all 0.2s ease;
  margin-left: 13px;
}

.theme-toggle:hover,
.history-toggle:hover {
  background-color: rgba(255, 255, 255, 0.1);
}

.icon-sun,
.icon-moon,
.icon-history,
.icon-close {
  display: inline-block;
  width: 20px;
  height: 20px;
  background-size: contain;
  background-repeat: no-repeat;
}

.icon-sun {
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath fill='currentColor' d='M12 18a6 6 0 1 1 0-12 6 6 0 0 1 0 12zm0-2a4 4 0 1 0 0-8 4 4 0 0 0 0 8zM11 1h2v3h-2V1zm0 19h2v3h-2v-3zM3.515 4.929l1.414-1.414L7.05 5.636 5.636 7.05 3.515 4.93zM16.95 18.364l1.414-1.414 2.121 2.121-1.414 1.414-2.121-2.121zm2.121-14.85l1.414 1.415-2.121 2.121-1.414-1.414 2.121-2.121zM5.636 16.95l1.414 1.414-2.121 2.121-1.414-1.414 2.121-2.121zM23 11v2h-3v-2h3zM4 11v2H1v-2h3z'/%3E%3C/svg%3E");
}

.icon-moon {
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath fill='currentColor' d='M10 7a7 7 0 0 0 12 4.9v.1c0 5.523-4.477 10-10 10S2 17.523 2 12 6.477 2 12 2h.1A6.977 6.977 0 0 0 10 7zm-6 5a8 8 0 0 0 15.062 3.762A9 9 0 0 1 8.238 4.938 8 8 0 0 0 4 12z'/%3E%3C/svg%3E");
}

.icon-history {
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath fill='currentColor' d='M12 2c5.523 0 10 4.477 10 10s-4.477 10-10 10S2 17.523 2 12h2a8 8 0 1 0 1.865-5.135L8 9H2V3l2.447 2.446A9.98 9.98 0 0 1 12 2zm1 5v4.585l3.243 3.243-1.415 1.415L11 12.413V7h2z'/%3E%3C/svg%3E");
}

.icon-close {
  line-height: 36px;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath fill='currentColor' d='M12 10.586l4.95-4.95 1.414 1.414-4.95 4.95 4.95 4.95-1.414 1.414-4.95-4.95-4.95 4.95-1.414-1.414 4.95-4.95-4.95-4.95 1.414-1.414 4.95 4.95z'/%3E%3C/svg%3E");
}

.calculator-content {
  display: flex;
  position: relative;
  transition: all 0.3s ease;
}

.calculator-main {
  width: 320px;
  transition: all 0.3s ease;
}

.history-open .calculator-main {
  transform: translateX(-150px);
}

.calculator-display {
  padding: 20px;
  text-align: right;
  min-height: 90px;
  cursor: text;
}

.expression {
  min-height: 24px;
  font-size: 18px;
  margin-bottom: 8px;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.result {
  font-size: 36px;
  font-weight: 500;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.calculator-keypad {
  display: grid;
  grid-template-rows: repeat(5, 1fr);
  padding: 15px;
  gap: 10px;
}

.row {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: 10px;
}

button {
  border: none;
  border-radius: 12px;
  padding: 16px 8px;
  font-size: 20px;
  font-weight: 500;
  cursor: pointer;
  transition: all 0.2s ease;
  box-shadow: 0 2px 5px rgba(0, 0, 0, 0.2);
}
.button {
  cursor: pointer;
  transition: all 0.2s ease;
  box-shadow: 0 2px 5px rgba(0, 0, 0, 0.2);
}

button:hover,
.button:hover {
  transform: translateY(-2px);
}

button:active,
.button:active {
  transform: translateY(1px);
}

.func {
  background-color: #e53e3e;
  color: white;
}

.func:hover {
  background-color: #c53030;
}

.operator {
  background-color: #3182ce;
}

.operator:hover {
  background-color: #2b6cb0;
}

.equals {
  background-color: #38a169;
  grid-column: span 2;
}

.equals:hover {
  background-color: #2f855a;
}

.calculator-history {
  position: absolute;
  right: 0;
  top: 0;
  width: 300px;
  height: 100%;
  background-color: inherit;
  border-left: 1px solid;
  z-index: 10;
  overflow-y: auto;
}

.history-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 15px;
  border-bottom: 1px solid;
}

.close-history {
  background: transparent;
  border: none;
  width: 30px;
  height: 30px;
  border-radius: 50%;
  display: flex;
  align-items: center;
  justify-content: center;
  cursor: pointer;
  transition: all 0.2s ease;
}

.close-history:hover {
  background-color: rgba(0, 0, 0, 0.1);
}

.history-items {
  padding: 0 15px;
}

.history-item {
  padding: 12px 0;
  border-bottom: 1px solid;
  cursor: pointer;
  transition: background-color 0.2s;
}

.history-item:hover {
  background-color: rgba(255, 255, 255, 0.1);
}

.history-item:last-child {
  border-bottom: none;
}

.history-expression {
  font-size: 14px;
  color: #a0aec0;
  margin-bottom: 4px;
}

.history-result {
  font-size: 18px;
  font-weight: 500;
}

.empty-history {
  text-align: center;
  padding: 20px;
  color: #a0aec0;
}

.history-slide-enter-active,
.history-slide-leave-active {
  transition: transform 0.3s ease;
}

.history-slide-enter-from,
.history-slide-leave-to {
  transform: translateX(100%);
}

/* 暗黑主题 */
.dark {
  background-color: #2d3748;
  color: white;
}

.dark .calculator-display {
  background-color: #1a202c;
}

.dark .expression {
  color: #a0aec0;
}

.dark .result {
  color: white;
}

.dark .calculator-keypad {
  background-color: #1a202c;
}

.dark button,
.dark .button {
  background-color: #4a5568;
  color: white;
}

.dark button:hover {
  background-color: #718096;
}

.dark .func {
  background-color: #e53e3e;
}

.dark .func:hover {
  background-color: #c53030;
}

.dark .operator {
  background-color: #3182ce;
}

.dark .operator:hover {
  background-color: #2b6cb0;
}

.dark .equals {
  background-color: #38a169;
}

.dark .equals:hover {
  background-color: #2f855a;
}

.dark .calculator-history {
  background-color: #2d3748;
  border-left-color: #4a5568;
}

.dark .history-header {
  border-bottom-color: #4a5568;
}

.dark .history-item {
  border-bottom-color: #4a5568;
}

.dark .close-history {
  color: white;
}

.dark .close-history:hover {
  background-color: rgba(255, 255, 255, 0.1);
}

/* 明亮主题 */
.light {
  background-color: #f7fafc;
  color: #2d3748;
}

.light .calculator-display {
  background-color: #edf2f7;
}

.light .expression {
  color: #718096;
}

.light .result {
  color: #2d3748;
}

.light .calculator-keypad {
  background-color: #edf2f7;
}

.light button {
  background-color: #e2e8f0;
  color: #2d3748;
}

.light button:hover {
  background-color: #cbd5e0;
}

.light .func {
  background-color: #f56565;
  color: white;
}

.light .func:hover {
  background-color: #e53e3e;
}

.light .operator {
  background-color: #4299e1;
}

.light .operator:hover {
  background-color: #3182ce;
}

.light .equals {
  background-color: #48bb78;
}

.light .equals:hover {
  background-color: #38a169;
}

.light .calculator-history {
  background-color: #f7fafc;
  border-left-color: #e2e8f0;
}

.light .history-header {
  border-bottom-color: #e2e8f0;
}

.light .history-item {
  border-bottom-color: #e2e8f0;
}

.light .close-history {
  color: #4a5568;
}

.light .close-history:hover {
  background-color: rgba(0, 0, 0, 0.05);
}
</style>
